package modelo.red;

import java.util.ArrayList;
import java.util.List;

import javax.persistence.Entity;
import javax.persistence.FetchType;
import javax.persistence.GeneratedValue;
import javax.persistence.Id;
import javax.persistence.ManyToOne;
import javax.persistence.OneToMany;
import javax.persistence.OneToOne;
import javax.persistence.Table;

import modelo.regionRiego.RegionRiego;

import org.hibernate.Query;
import org.hibernate.Session;

@Entity
@Table(name="malla")
public class Malla {
	private long id;
	private String nombre;
	private String descripcion;
	private int dimension;
	private double esteMin;
	private double esteMax;
	private double norteMin;
	private double norteMax;
	private double zetaMin;
	private double zetaMax;
	private int tipo;
	private int nroFil;
	private int nroCol;
	private RegionRiego regionRiego;

	
	private List<NorteSur> ejeNorteSur;
	private List<EsteOeste> ejeEsteOeste;
	private List<Zeta> ejeZeta;
	private List<ValorAtributo> listaPunto;
	private List<AtributoMalla> listaAtributo;
	
	
	@Id
	@GeneratedValue
	public long getId() {
		return id;
	}
	public void setId(long id) {
		this.id = id;
	}
	public String getNombre() {
		return nombre;
	}
	public void setNombre(String nombre) {
		this.nombre = nombre;
	}
	public String getDescripcion() {
		return descripcion;
	}
	public void setDescripcion(String descripcion) {
		this.descripcion = descripcion;
	}
	public int getDimension() {
		return dimension;
	}
	public void setDimension(int dimension) {
		this.dimension = dimension;
	}
	public double getEsteMin() {
		return esteMin;
	}
	public void setEsteMin(double esteMin) {
		this.esteMin = esteMin;
	}
	public double getEsteMax() {
		return esteMax;
	}
	public void setEsteMax(double esteMax) {
		this.esteMax = esteMax;
	}
	public double getNorteMin() {
		return norteMin;
	}
	public void setNorteMin(double norteMin) {
		this.norteMin = norteMin;
	}
	public double getNorteMax() {
		return norteMax;
	}
	public void setNorteMax(double norteMax) {
		this.norteMax = norteMax;
	}
	
	public double getZetaMin() {
		return zetaMin;
	}
	public void setZetaMin(double zetaMin) {
		this.zetaMin = zetaMin;
	}

	public double getZetaMax() {
		return zetaMax;
	}

	public void setZetaMax(double zetaMax) {
		this.zetaMax = zetaMax;
	}
		
	public int getNroFil() {
		return nroFil;
	}
	public void setNroFil(int nroFil) {
		this.nroFil = nroFil;
	}
	public int getNroCol() {
		return nroCol;
	}
	public void setNroCol(int nroCol) {
		this.nroCol = nroCol;
	}
	public int getTipo() {
		return tipo;
	}
	public void setTipo(int tipo) {
		this.tipo = tipo;
	}
	@OneToMany(mappedBy = "malla")
	public List<NorteSur> getEjeNorteSur() {
		return ejeNorteSur;
	}
	public void setEjeNorteSur(List<NorteSur> ejeNorteSur) {
		this.ejeNorteSur = ejeNorteSur;
	}
	@OneToMany(mappedBy = "malla")
	public List<EsteOeste> getEjeEsteOeste() {
		return ejeEsteOeste;
	}
	public void setEjeEsteOeste(List<EsteOeste> ejeEsteOeste) {
		this.ejeEsteOeste = ejeEsteOeste;
	}
	@OneToMany(mappedBy = "malla")
	public List<Zeta> getEjeZeta() {
		return ejeZeta;
	}
	public void setEjeZeta(List<Zeta> ejeZeta) {
		this.ejeZeta = ejeZeta;
	}
	@OneToMany(fetch = FetchType.LAZY, mappedBy = "malla")
	public List<ValorAtributo> getListaPunto() {
		return listaPunto;
	}
	public void setListaPunto(List<ValorAtributo> listaPunto) {
		this.listaPunto = listaPunto;
	}
	@OneToMany(mappedBy = "malla")
	public List<AtributoMalla> getListaAtributo() {
		return listaAtributo;
	}
	public void setListaAtributo(List<AtributoMalla> listaAtributo) {
		this.listaAtributo = listaAtributo;
	}
	@ManyToOne
	public RegionRiego getRegionRiego() {
		return regionRiego;
	}
	public void setRegionRiego(RegionRiego regionRiego) {
		this.regionRiego = regionRiego;
	}
	
	public void inicializarListaPunto() {
		listaPunto = new ArrayList<ValorAtributo>();
	}
	
	public void agregarPunto(ValorAtributo punto){
		listaPunto.add(punto);
	}
	
	public void inicializarEjeEsteOeste() {
		ejeEsteOeste = new ArrayList<EsteOeste>();
	}
	
	public void agregarPuntoEjeEsteOeste(EsteOeste punto){
		ejeEsteOeste.add(punto);
	}
	
	public void inicializarEjeNorteSur(){
		ejeNorteSur = new ArrayList<NorteSur>();
	}
	
	public void agregarPuntoEjeNorteSur(NorteSur punto){
		ejeNorteSur.add(punto);
	}
	
	public void inicializarEjeZeta(){
		ejeZeta = new ArrayList<Zeta>();
	}
	public void agregarEjeZeta(Zeta punto){
		ejeZeta.add(punto);
	}

	
	public void inicializarAtributoMalla(){
		listaAtributo = new ArrayList<AtributoMalla>();
	}
	public void agregarAtributoMalla(AtributoMalla atributo){
		listaAtributo.add(atributo);
	}
	public Pixel validarPunto(double norte, double este) {
		boolean encontradoLat = false;
		boolean encontradoLong = false;
		int indEjeNS =0;
		int indEjeEO = 0;
		int indMenor = 0;
		int indMayor = ejeNorteSur.size() - 1;
		if(norte >= ejeNorteSur.get(indMenor).getValor() && norte <= ejeNorteSur.get(indMayor).getValor()) {
			for(int i=1; i<indMayor; i++){
				if(norte >= ejeNorteSur.get(i).getValor()){
					indEjeNS = i;
				}
				else {
					break;
				}
			}
			encontradoLat = true;
		}
		
		indMayor = ejeEsteOeste.size() - 1;
		if(este >= ejeEsteOeste.get(indMenor).getValor() && este <= ejeEsteOeste.get(indMayor).getValor()) {
			for(int i=1; i<indMayor; i++){
				if(este > ejeEsteOeste.get(i).getValor()){
					indEjeEO = i;
					
				}
				else {
					break;
				}
			}
			encontradoLong = true;
		}
		
		if(!encontradoLong && encontradoLat) {
			return null;
		}
		Pixel pixel = new Pixel();
		pixel.setMalla(this);
		pixel.setNorte(norte);
		pixel.setEste(este);
		pixel.setEsteMin(ejeEsteOeste.get(indEjeEO).getId());
		pixel.setEsteMax(ejeEsteOeste.get(indEjeEO+1).getId());
		pixel.setNorteMin(ejeNorteSur.get(indEjeNS).getId());
		pixel.setNorteMax(ejeNorteSur.get(indEjeNS+1).getId());
		pixel.setIndEsteMin(indEjeEO);
		pixel.setIndEsteMax(indEjeEO+1);
		pixel.setIndNorteMin(indEjeNS);
		pixel.setIndNorteMax(indEjeNS+1);
//		System.out.println("indEjeEO " +indEjeEO + " indEjeNS" + indEjeNS);
		return pixel;
	}
}
